import { IntervalTimeUnit } from "../types/L_Type"
import UnitMoveEvent, { UNIT_MOVE_EVENT_DTL } from "../event/eventdef/UnitMoveEvent"
import IDGen from "../utils/IDGen"
import L_Run from "../utils/L_Run"


export type SPD_TIMER_TRSF={
    inteverUnit:IntervalTimeUnit,
    integerVal:number
    onceMoveDis:number
    execTimes:number
}

/**移动的对象/单位 所有移动的父类  根据此类进行扩展  */
export default class MovingObject {

    mid: number
    /**移动的单位 */
    movingUnit: unit
  
    /**移动速度  每秒飞行x码 (1-2000)*/
    disPerSecond!:number 
    
   
    /**箭矢移动绑定的事件 */
    movingEvent!:UnitMoveEvent


    constructor(
        movingUnit: unit
    ) {
        this.mid = IDGen.getNextId('MOVING_UNIT')
        this.movingUnit = movingUnit
    }


    public  moveToXY(x:number,y:number,disPerSecond:number,evCallback?:UNIT_MOVE_EVENT_DTL){
        this.moveToXYBySSPD(x,y,disPerSecond,undefined,evCallback)
    }

    public  angleMoveWithDis(dis:number,x:number,y:number,disPerSecond:number,evCallback?:UNIT_MOVE_EVENT_DTL){
        this.moveToXYBySSPD(x,y,disPerSecond,dis,evCallback)
    }

    /**以完全自定义的方式进行移动 sppedPerSecond参数版本 */
    public moveByCustomS(disPerSecond:number,targetDis:number,
        evCallback?:UNIT_MOVE_EVENT_DTL, customMoveFunc?:(hasExecNums:number,moveUnit:unit)=>{x:number,y:number}){
        let spdTimerParamMap=this.trsfSpdDToTimerParamMap(disPerSecond,targetDis)
        this.movingEvent=new UnitMoveEvent('CUSTOM',spdTimerParamMap.inteverUnit,spdTimerParamMap.integerVal,spdTimerParamMap.execTimes,spdTimerParamMap.onceMoveDis,0,this.movingUnit,this.mid,evCallback,customMoveFunc)
        this.movingEvent.beAddedAndExec()
    }

    /**以完全自定义的方式进行移动 timer参数版本 */
    public moveByCustomT(inteverUnit:IntervalTimeUnit,integerVal:number,execTimes:number,onceMoveDis:number,
                        evCallback?:UNIT_MOVE_EVENT_DTL, customMoveFunc?:(hasExecNums:number,moveUnit:unit)=>{x:number,y:number}){
        this.movingEvent=new UnitMoveEvent('CUSTOM',inteverUnit,integerVal,execTimes,onceMoveDis,0,this.movingUnit,this.mid,evCallback,customMoveFunc)
        this.movingEvent.beAddedAndExec()
    }

    /**提前结束移动 */
    public stopMoving(){
        this.movingEvent.endImmed();
    }

    /**
     * 箭矢/单位 在执行速度计算转换后 移动到指定x y坐标
     * @param x 
     * @param y 
     * @param disPerSecond 秒距离（码）
     * @param targetDis 指定移动距离 默认不设置移动到XY 但是设置后XY坐标成为确认方向的参考 不再决定最终位置
     * @param cDmgConfig 箭矢通用伤害函数配置
     * @param eventCallback  不适用箭矢通用伤害函数 但是想自己配置移动事件回调的情况  与cDmgConfig为互斥参数
     */
    private  moveToXYBySSPD(x:number,y:number,disPerSecond:number,targetDis?:number, evCallback?:UNIT_MOVE_EVENT_DTL){
        this.disPerSecond=disPerSecond
        // let inteverUnit:IntervalTimeUnit
        // let integerVal:number
        // let onceMoveDis:number=1
        // let execTimes:number
        
        let targetDisR=(targetDis!=undefined?targetDis:L_Run.getDisOfUnitToXY(this.movingUnit,x,y))
        let spdTimerParamMap=this.trsfSpdDToTimerParamMap(disPerSecond,targetDisR)
        let angel=L_Run.getAngleWithUnitToXY(this.movingUnit,x,y)
        this.movingEvent=new UnitMoveEvent('LINE',spdTimerParamMap.inteverUnit,spdTimerParamMap.integerVal,spdTimerParamMap.execTimes,spdTimerParamMap.onceMoveDis,angel,this.movingUnit,this.mid,evCallback)
        this.movingEvent.beAddedAndExec()
    }

    protected trsfSpdDToTimerParamMap(disPerSecond:number,targetDis:number):SPD_TIMER_TRSF{
        let inteverUnit:IntervalTimeUnit
        let integerVal:number
        let onceMoveDis:number=1
        let execTimes:number
        if(disPerSecond>=0 && disPerSecond<=100){
            inteverUnit='TENTH_OF_SEC'
            integerVal=1
            onceMoveDis=disPerSecond/10
            execTimes=targetDis/onceMoveDis
        }else if(disPerSecond>100 && disPerSecond<500){
            inteverUnit='HUNDRE_OF_SEC'
            integerVal=5
            onceMoveDis=disPerSecond/20   //20=1秒/0.01*integerVal
            execTimes=targetDis/onceMoveDis
        }else if(disPerSecond>500 && disPerSecond<1000){
            inteverUnit='HUNDRE_OF_SEC'
            integerVal=4
            onceMoveDis=disPerSecond/25
            execTimes=targetDis/onceMoveDis
        }else if(disPerSecond>1000){
            inteverUnit='HUNDRE_OF_SEC'
            integerVal=3
            onceMoveDis=disPerSecond/33
            execTimes=targetDis/onceMoveDis
        }else{
            //负数 无法执行的情况 原地挪一下 正常不可能发生
            inteverUnit='SECONDS'
            integerVal=1
            onceMoveDis=1
            execTimes=1
        }
        return {inteverUnit,integerVal,onceMoveDis,execTimes}
    }

}  